package main

import (
	"fmt"
	"time"
)

type My struct {
	name string
}

func main() {
	fmt.Println("hello world")

	fmt.Println()
	var a string = "ddd"
	b := 2
	fmt.Println(a)
	fmt.Println(b)

	var qs My
	qs.name = "bbb"
	fmt.Println(qs.name)

	//数组遍历

	var arr = [...]int{1, 2, 3, 4, 5, 6, 7, 8, 9}

	for i := 0; i < len(arr); i++ {
		fmt.Println(arr[i])
	}

	for index, value := range arr {
		fmt.Printf("%d=%d\n", index, value)
		arr[index] += 2
	}

	for _, va := range arr {
		fmt.Println(va)
	}

	s0 := arr[1:3] //含头不含尾
	s0 = append(s0, 90)
	for _, va := range s0 {
		fmt.Println(va)
	}

	var str = "b"

	switch str {

	case "a":
		fmt.Println("a")
	case "b":
		fmt.Println("b1")
	case "h":
		fmt.Println("c")
		fallthrough //向下传，会打出default
	default:
		fmt.Println("default")

	}

	fmt.Println("==========数组遍历=======")

	var myarr0 [5]int
	fmt.Println("数组初始值:", myarr0)

	myarr := [...]string{"1", "2", "3", "4", "5"}
	arrOver(myarr) //相当于值传递，不会被修改
	fmt.Println(myarr[0])

	fmt.Println("==========切片遍历=======")

	var mysli0 []int //初始为nil
	fmt.Println("切片初始值:", mysli0 == nil)
	mysli0 = make([]int, 2, 4)
	fmt.Println("切片初始值2:", mysli0, len(mysli0), cap(mysli0))

	mysli := myarr[0:]
	sliceOver(mysli) //相当于引用传递，会被修改,从数组创建的切片包含了原数组的指针，切片修改了，原数组的值也修改了，但如果切片扩容了，就和原数组没关系了
	fmt.Println(mysli[0])
	fmt.Println(myarr[0])

	fmt.Println("==========map遍历=======")
	var mymap0 map[string]string //初始为nil
	fmt.Println("map初始值:", mymap0 == nil)

	mymap := map[string]string{"name": "jack", "hfe": "12"}
	mapOver(mymap) //相当于引用传递，会被修改,
	fmt.Println(mymap["name"])

	fmt.Println("==========接口遍历=======")
	var IF interface{}     //空接口可以是任意类型
	fmt.Println(IF == nil) //nil

	IF = 1
	fmt.Println(IF)
	IF = "fdfd"
	fmt.Println(IF)
	IF = arrOver
	fmt.Println(IF)

	fmt.Println("==========接口继承=======")

	//struct 也相当于值传递，会递归传(struct中的字段)
	myf := []myIF{}
	//append(myf,Anim{  //报错
	//	age: 12,
	//	weight: 12.78,
	//})

	p := Person{
		a: "good boy",
		Anim: Anim{
			age:    12,
			weight: 45.45,
		},
	}
	//myf=append(myf, &p)
	//fmt.Println(myf[0])
	//p.jump()

	var cc myIF
	cc = &p
	cc.jump()
	//如果是值接收者实现的接口，不论结构体类型是值类型还是指针类型，接口变量都可以接受
	//如果是指针接收者的接口，只能接受指针类型的对象。

	fmt.Println("myf:", myf, len(myf), p.a)

	for i := 0; i < 10; i++ {
		go fmt.Println("i=", i)
	}
	time.Sleep(time.Second)
}

type myIF interface {
	jump()
}

type Anim struct {
	weight float64
	age    int
}

func (p *Person) jump() {
	fmt.Println("people jump", p.weight, p.a)
	p.a = "bad boy"
}

type Person struct {
	a string
	//嵌入类型,可以直接用
	Anim
}

func arrOver(arr [5]string) {
	arr[0] = "hello"
}

func sliceOver(arr []string) {
	arr[0] = "hello"
}

func mapOver(m map[string]string) {
	m["name"] = "lily"
}

func print_map(m map[string]interface{}) {
	for k, v := range m {
		switch value := v.(type) {
		case nil:
			fmt.Println(k, "is nil", "null")
		case string:
			fmt.Println(k, "is string", value)
		case int:
			fmt.Println(k, "is int", value)
		case float64:
			fmt.Println(k, "is float64", value)
		case []interface{}:
			fmt.Println(k, "is an array:")
			for i, u := range value {
				fmt.Println(i, u)
			}
		case map[string]interface{}:
			fmt.Println(k, "is an map:")
			print_map(value)
		default:
			fmt.Println(k, "is unknown type", fmt.Sprintf("%T", v))
		}
	}
}
